/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */


import impsoft.scripting.ibot.structs.AryanTile;
import impsoft.scripting.types.ColorSkeltonScriptable;
import impsoft.scripting.types.parallel.scriptjobs.ScriptJob;
import java.awt.Polygon;
import java.util.ArrayList;

/**
 *
 * @author Jake
 */
public class Walker {

    private ColorSkeltonScriptable cs;

    public Walker(ColorSkeltonScriptable cs) {
        this.cs = cs;
    }

    public void walkToTileUsingScreen(AryanTile at) throws InterruptedException {
        boolean atdest = false;
        while (!atdest) {
            AryanTile c = this.cs.getLocation();
            AryanTile[] aroundus = getTilesAroundUs(c);
            int dis = 999999;
            AryanTile tc = null;
            for (AryanTile atn : aroundus) {
                if (atn.distanceTo(at) < dis) {
                    dis = atn.distanceTo(at);
                    tc = atn;
                }
            }
            if (tc == null) {
                return;
            }
            int[] obj3D = new int[]{-15, 15, -15, 15, 0, 5};
            Polygon p = tc.getGameScreenLocation(cs,
                    obj3D[0],
                    obj3D[1],
                    obj3D[2],
                    obj3D[3],
                    obj3D[4],
                    obj3D[5]);
            cs.mouseClickLeft(p.getBounds());
            sleepTillStill(tc);
        }

    }

    private void sleepTillStill(AryanTile at) throws InterruptedException {
        for (int i = 0; i < 100; i++) {
            if (cs.isMoving()) {
                i = 0;
            }
            cs.sleep(10);
            if (at.distanceTo(cs.getLocation()) < 5) {
                return;
            }
        }
    }

    private AryanTile[] getTilesAroundUs(AryanTile c) {
        ArrayList<AryanTile> al = new ArrayList<AryanTile>();
        for (int x = -10; x < 10; x++) {
            for (int y = -10; y < 10; y++) {
                int[] obj3D = new int[]{-15, 15, -15, 15, 0, 5};
                Polygon p = (new AryanTile(c.x + x, c.y + y).getGameScreenLocation(cs,
                        obj3D[0],
                        obj3D[1],
                        obj3D[2],
                        obj3D[3],
                        obj3D[4],
                        obj3D[5]));
                if (p != null) {
                    al.add(new AryanTile(c.x + x, c.y + y));
                }
            }

        }
        return al.toArray(new AryanTile[al.size()]);
    }

    public boolean walkToTileMultiple(AryanTile... at) throws InterruptedException {
        for (int i = 0; i < at.length; i++) {
            ScriptJob sj = cs.theParallelWalking.walkToTile(at[i]);
            sj.runV();
            while (!sj.isDone()) {
                cs.sleep(cs.random(500, 750));
            }
            sj.safeKill();
            sj = null;
        }
        return true;
    }

    public boolean walkToTileArray(AryanTile[] at) throws InterruptedException {
        for (int i = getNextTileIndex(at); i < at.length; i++) {
            log(at.length);
            ScriptJob sj = cs.theParallelWalking.walkToTile(at[i]);
            sj.runV();
            while (!sj.isDone()) {
                cs.sleep(cs.random(500, 750));
            }
            sj.safeKill();
            sj = null;
        }
        return true;
    }

    public boolean walkToEnd(AryanTile[] at) throws InterruptedException {
        for (int i = (getNextTileIndex(at)); i < at.length; i++) {
            log("Walking to the end of the array, step " + (i + 1) + " out of " +
                    at.length);
            ScriptJob sj = cs.theParallelWalking.walkToTile(at[i]);
            sj.runV();
            while (!sj.isDone()) {
                new Rotation().run();
                cs.sleep(cs.random(500, 750));
                if (cs.getLocation().distanceTo(at[i]) < 10) {
                    break;
                }
            }
            sj.safeKill();
            sj = null;
        }
        return true;
    }

    public int getNextTileIndex(AryanTile[] at) {
        AryanTile previous = null;
        int index = 0;
        if (at == null) {
            return -1;
        }
        for (int i = 0; i < at.length; i++) {
            if (previous == null) {
                previous = at[i];
            } else {
                try {
                    if (cs.getLocation().distanceTo(previous) >
                            cs.getLocation().distanceTo(at[i])) {
                        if (at[i + 1] != null) {
                            if (cs.getLocation().distanceTo(previous) >
                                    cs.getLocation().distanceTo(at[i]) &&
                                    cs.getLocation().distanceTo(at[i]) <
                                    cs.getLocation().distanceTo(at[i + 1])) {
                                index = i;
                            }
                        } else {
                            return i;
                        }
                    }
                } catch (ArrayIndexOutOfBoundsException AIOOBE) {
                    return i;
                }
            }
        }
        return 1;
    }

    public boolean walkToStart(AryanTile[] at) throws InterruptedException {
        for (int i = getNextTileIndex(at) - 1; i >= 0; i--) {
            log("Walking to the start of the array, step " + (i + 1) + " out of " +
                    at.length);
            ScriptJob sj = cs.theParallelWalking.walkToTile(at[i]);
            sj.runV();
            while (!sj.isDone()) {
                new Rotation().run();
                cs.sleep(cs.random(500, 750));
                if (cs.getLocation().distanceTo(at[i]) < 10) {
                    break;
                }

            }
            sj.safeKill();
            sj = null;
        }
        return true;
    }

    private void log(Object a) {
        cs.log("[PLANK WALKER] " + a);
    }

    class Rotation extends Thread {

        @Override
        public void run() {
            setName("RotationThread");
            try {
                int random = cs.random(0, 20000);
                switch (random) {
                    case 1:
                        cs.theCamera.setPitchUp();
                        log("Set camera pitch up");
                        break;
                    case 2:
                        cs.theCamera.setYawToEast();
                        log("Set camera yaw east");
                        break;
                    case 3:
                        cs.theCamera.setYawToNorth();
                        log("Set camera yaw North");
                        break;
                    case 4:
                        cs.theCamera.setYawRandom();
                        log("Set camera yaw randomly");
                        break;
                    case 5:
                        cs.theCamera.setYawToNorthWest();
                        log("Set camera yaw to North-West");
                        break;
                    case 6:
                        cs.theCamera.setYawToNorthEast();
                        log("Set camera yaw to North-East");
                        break;
                    case 7:
                        cs.theCamera.setYawToNorthWest();
                        log("Set camera yaw to North-West");
                        break;
                    case 8:
                        cs.theCamera.setYawToSouth();
                        log("Set camera yaw to South");
                        break;
                    case 9:
                        cs.theCamera.setYawToSouthEast();
                        log("Set camera yaw to South-East");
                        break;
                    case 10:
                        cs.theCamera.setYawToSouthWest();
                        log("Set camera yaw to South-West");
                        break;
                    case 11:
                        cs.theCamera.setYawToWest();
                        log("Set camera yaw to West");
                        break;
                }
            } catch (InterruptedException e) {
                log("Error" + e);
            }
        }
    }
}